-module(shoutserver).

start() ->
	spawn(fun() ->
			start_parallel_server(3000),
			sleep(infinity)
			end
		).
		
start_parallel_server(Port) ->
	{ok, Socket} = gen_tcp:listen(Port, [binary, {packet, 0}, {reuseaddr, true}, {active, true}]),
	PidSongServer = spawn(fun() -> songs() end),
	spawn(fun() -> par_connect(Listen, PidSongServer) end).
	
par_connect(Listen, PidSongServer) ->
	{ok, Socket} = gen_tcp:accept(Listen),
	spawn(fun() -> par_connect(Listen, PidSongServer) end),
	inets:setopts(Socket, [{packet,0}, binary, {nodelay, true}, {active, true}]),
	get_request(Socket, PidSongServer, []).

get_request(Socket, PidSongServer, L) ->
	receive
		{tcp, Socket, Bin} ->
			L1 = L ++ binary_to_list(Bin),
			case split(L1, []) of
				more ->
					get_request(Socket, PidSongServer, L1);
				{Request, _Rest} ->
					got_request_from_client(Request, Socket, PidSongServer)
			end;
		{tcp_closed, Socket} ->
			void;
		_Any ->
			get_request(Socket, PidSongServer, L)
	end.
		
split("\r\n\r\n" ++ T, L) 	-> {reverse(L), T};
split([H|T], L) 			-> split(T, [H|L]);
split([], _)				-> more.

got_request_from_client(Request, Socket, PidSongServer) ->
	Cmds = string:tokens(Request, "\r\n"),
	Cmds1 = map(fun(I) -> string:tokens(I, " ") end, Cmds),
	is_request_for_stream(Cmds1),
	gen_tcp:send(Socket, [response()]),
	play_songs(Socket, PidSongServer, <<>>).
	
play_songs(Socket, PidSongServer, SoFar) ->
	Song = rpc(PidSongServer, randon_song),
	{File, PrintStr, Header} = unpack_song_descriptor(Song),
	case id3_tag_lengths:file(File) of
		error ->
			play_songs(Socket, PidSongServer, SoFar);
		{Start, Stop} ->
			io:format("Playing:~p~n", [PrintStr]),
			{ok, S} = file:open(File, [read, binary, raw]),
			SoFar1 = send_file(S, {0, Header}, Start, Stop, Socket, SoFar),
			file:close(S),
			play_songs(Socket, PidSongServer, SoFar1)
	end.
	
send_file(S, Header, Offset, Stop, Socket, SoFar) ->
	Need = 
		
sleep(T) ->
	receive
		after T
			true
	end.
